package bll

import (
	"context"
	"maya-service/store/mysql"

	"maya-service/model"
	"maya-service/model/entity"
	"maya-service/model/mapping"
	"maya-service/store"
	"time"
)

type order struct {
	iOrder store.IOrder
}

var Order = &order{
	iOrder: mysql.Order,
}

func init() {
	Register(Order)
}

func (a *order) init() func() {
	return func() {}
}

// Create
func (a *order) Create(ctx context.Context, in *model.OrderCreateRequest) error {
	var (
		err error
	)
	c := buildOrder(in)
	_, err = a.iOrder.Create(ctx, c)
	return err
}

// Update
func (a *order) Update(ctx context.Context, in *model.OrderUpdateRequest) error {
	var (
		dict = make(map[string]interface{})
	)

	if in.OrderId != nil {
		dict["order_id"] = in.OrderId
	}

	if in.CustomerId != nil {
		dict["customer_id"] = in.CustomerId
	}

	if in.OrderDate != nil {
		dict["order_date"] = in.OrderDate
	}

	if in.OrderStatus != nil {
		dict["order_status"] = in.OrderStatus
	}

	if in.TotalAmount != nil {
		dict["total_amount"] = in.TotalAmount
	}

	if in.PaymentMethod != nil {
		dict["payment_method"] = in.PaymentMethod
	}

	if in.ShippingAddress != nil {
		dict["shipping_address"] = in.ShippingAddress
	}

	if in.Remarks != nil {
		dict["remarks"] = in.Remarks
	}

	if in.OrderContext != nil {
		dict["order_context"] = in.OrderContext
	}

	if in.ExtraData != nil {
		dict["extra_data"] = in.ExtraData
	}

	if in.CreatedAt != nil {
		dict["created_at"] = in.CreatedAt
	}

	if in.UpdatedAt != nil {
		dict["updated_at"] = in.UpdatedAt
	}

	// do other update here
	updateAt := time.Now().Unix()
	in.UpdatedAt = &updateAt
	return a.iOrder.Update(ctx, in, dict)
}

// Delete
func (a *order) Delete(ctx context.Context, in *model.OrderDeleteRequest) error {
	return a.iOrder.Delete(ctx, in.Id)
}

// List
func (a *order) List(ctx context.Context, in *model.OrderListRequest) (*model.OrderListResponse, error) {
	var (
		err   error
		total int
		list  []*entity.Order
		out   = &model.OrderListResponse{}
	)

	if total, list, err = a.iOrder.List(ctx, in); err != nil {
		return nil, err
	}

	out.Total = total
	out.List = mapping.OrdersEntityToDto(list)

	return out, nil
}

// Find
func (a *order) Find(ctx context.Context, in *model.OrderInfoRequest) (*model.OrderInfo, error) {
	var (
		err  error
		data *entity.Order
		out  = &model.OrderInfo{}
	)

	if data, err = a.iOrder.Find(ctx, in); err != nil {
		return nil, err
	}

	out = mapping.OrderEntityToDto(data)
	return out, nil
}

// buildOrder build entity
func buildOrder(in *model.OrderCreateRequest) *entity.Order {

	ety := &entity.Order{}

	ety.OrderId = in.OrderId

	ety.OrderDate = in.OrderDate

	ety.OrderStatus = in.OrderStatus

	ety.PaymentMethod = in.PaymentMethod

	ety.ShippingAddress = in.ShippingAddress

	ety.Remarks = in.Remarks

	ety.OrderContext = in.OrderContext

	ety.CustomerId = in.CustomerId

	ety.ExtraData = in.ExtraData

	ety.CreatedAt = time.Now().Unix()

	ety.UpdatedAt = in.UpdatedAt

	return ety
}
